package io.shuttle.mbe

import android.os.Handler
import android.os.Looper
import androidx.test.platform.app.InstrumentationRegistry
import androidx.test.ext.junit.runners.AndroidJUnit4
import io.shuttle.mbe.core.Promise

import org.junit.Test
import org.junit.runner.RunWith

import org.junit.Assert.*
import java.util.Locale
import java.util.concurrent.TimeUnit

/**
 * Instrumented test, which will execute on an Android device.
 *
 * See [testing documentation](http://d.android.com/tools/testing).
 */
@RunWith(AndroidJUnit4::class)
class ExampleInstrumentedTest2 {
    @Test
    fun useAppContext() {
        // Context of the app under test.
        val appContext = InstrumentationRegistry.getInstrumentation().targetContext
        assertEquals("io.shuttle.mbe_core", appContext.packageName)
    }

    val mainHandler: Handler = Handler(Looper.getMainLooper())

    @Test
    fun main() {
        println("=== Promise 使用示例 ===\n")
        basicPromiseExample()
        chainedPromiseExample()
        errorHandlingExample()
        futureInterfaceExample()
        promiseAllExample()
        staticMethodsExample()
        try {
            Thread.sleep(8000)
        } catch (e: InterruptedException) {
            e.printStackTrace()
        }
    }

    /**
     * 示例1: 基本的 Promise 使用
     */
    private fun basicPromiseExample() {
        println("1. 基本 Promise 使用:")

        val promise: Promise<String?> = Promise { resolve, reject ->
            // 模拟异步操作
            Thread(Runnable {
                try {
                    Thread.sleep(1000)
                    resolve?.resolve("异步操作完成!")
                } catch (e: InterruptedException) {
                    reject?.reject(e)
                }
            }).start()
        }

        promise.then { result ->
            println("   结果: $result")
            result
        }

        println("   Promise 已创建，等待结果...\n")
    }

    /**
     * 示例2: 链式调用
     */
    private fun chainedPromiseExample() {
        println("2. 链式调用:")

        val promise: Promise<Int?> = Promise { resolve, reject ->
            Thread(Runnable {
                try {
                    Thread.sleep(1500)
                    resolve?.resolve(10)
                } catch (e: InterruptedException) {
                    reject?.reject(e)
                }
            }).start()
        }

        val catchError = promise
            .then { num ->
                println("   第一步: $num")
                num?.times(2)
            }
            .then { num ->
                println("   第二步: $num")
                num?.plus(5)
            }
            .then { num ->
                println("   最终结果: $num")
                num
            }
            .catchError { error ->
                println("   发生错误: " + error?.message)
                0
            }

        println("   链式调用已设置，等待执行...\n")
    }

    /**
     * 示例3: 错误处理
     */
    private fun errorHandlingExample() {
        println("3. 错误处理:")

        val promise: Promise<String?> = Promise { resolve, reject ->
            Thread(Runnable {
                try {
                    Thread.sleep(500)
                    // 模拟错误
                    reject?.reject(RuntimeException("模拟的网络错误"))
                } catch (e: InterruptedException) {
                    reject?.reject(e)
                }
            }).start()
        }

        promise
            .then { result ->
                println("   成功: $result")
                result
            }
            .catchError { error ->
                println("   捕获错误: " + error?.message)
                "默认值"
            }
            .then { result ->
                println("   恢复后的结果: $result")
                result
            }

        println("   错误处理示例已设置...\n")
    }

    /**
     * 示例4: 作为 Future 使用
     */
    private fun futureInterfaceExample() {
        println("4. 作为 Future 接口使用:")

        val promise: Promise<String?> = Promise { resolve, reject ->
            Thread(Runnable {
                try {
                    Thread.sleep(2000)
                    resolve?.resolve("Future 接口结果")
                } catch (e: InterruptedException) {
                    reject?.reject(e)
                }
            }).start()
        }


        // 在新线程中使用 Future 接口
        Thread(Runnable {
            try {
                println("   等待 Future 结果...")
                val result: String? = promise.get(3, TimeUnit.SECONDS)
                println("   Future.get() 结果: $result")
                println("   isDone: " + promise.isDone)
                println("   isCancelled: " + promise.isCancelled)
            } catch (e: Exception) {
                println("   Future 获取失败: " + e.message)
            }
        }).start()

        println("   Future 接口测试已启动...\n")
    }

    /**
     * 示例5: Promise.all 使用
     */
    private fun promiseAllExample() {
        println("5. Promise.all 使用:")


        // 创建多个 Promise
        val promise1: Promise<String?> = Promise { resolve, reject ->
            Thread(Runnable {
                try {
                    Thread.sleep(1000)
                    resolve?.resolve("任务1完成")
                } catch (e: InterruptedException) {
                    reject?.reject(e)
                }
            }).start()
        }

        val promise2: Promise<String?> = Promise { resolve, reject ->
            Thread(Runnable {
                try {
                    Thread.sleep(1500)
                    resolve?.resolve("任务2完成")
                } catch (e: InterruptedException) {
                    reject?.reject(e)
                }
            }).start()
        }

        val promise3: Promise<String?> = Promise { resolve, reject ->
            Thread(Runnable {
                try {
                    Thread.sleep(800)
                    resolve?.resolve("任务3完成")
                } catch (e: InterruptedException) {
                    reject?.reject(e)
                }
            }).start()
        }

        val promises: MutableList<Promise<String?>> =
            mutableListOf(promise1, promise2, promise3)

        Promise.all<String>(promises)
            .then { results ->
                println("   所有任务完成:")
                for (i in 0..<results!!.size) {
                    println("     " + (i + 1) + ". " + results[i])
                }
                results
            }
            .catchError { error ->
                println("   Promise.all 失败: " + error?.message)
                mutableListOf("默认结果")
            }

        println("   Promise.all 已启动，等待所有任务完成...\n")
    }

    /**
     * 示例6: 静态工厂方法
     */
    private fun staticMethodsExample() {
        println("6. 静态工厂方法:")


        // Promise.resolve
        Promise.resolve("立即完成的值")
            .then { result ->
                println("   Promise.resolve: $result")
                result
            }


        // Promise.reject
        Promise.reject<String>(RuntimeException("立即拒绝的错误"))
            .catchError { error ->
                println("   Promise.reject: " + error?.message)
                "错误已处理"
            }
            .then { result ->
                println("   恢复结果: $result")
                result
            }

        println("   静态方法示例已执行...\n")
    }

    /**
     * 模拟网络请求
     */
    private fun simulateNetworkRequest(url: String?, delay: Int): Promise<String?> {
        return Promise { resolve, reject ->
            Thread(Runnable {
                try {
                    println("   开始请求: $url")
                    Thread.sleep(delay.toLong())


                    // 模拟随机失败
                    if (Math.random() < 0.2) {
                        reject?.reject(RuntimeException("网络请求失败: $url"))
                    } else {
                        resolve?.resolve("数据来自: $url")
                    }
                } catch (e: InterruptedException) {
                    reject?.reject(e)
                }
            }).start()
        }
    }

    /**
     * 模拟数据处理
     */
    private fun processData(data: String): Promise<String?> {
        return Promise { resolve, reject ->
            Thread(Runnable {
                try {
                    Thread.sleep(300)
                    resolve?.resolve("处理后的数据: " + data.uppercase(Locale.getDefault()))
                } catch (e: InterruptedException) {
                    reject?.reject(e)
                }
            }).start()
        }
    }
}